# @Time : 2020/8/27 14:01
# @Author : Fioman 
# @Phone : 13149920693
"""
一个简单的阈值分割,大于T的被设置为255,其他的小于等于T被设置为0. 阈值分割的标志是CV.THRES_BINARY.
CV.THRES_BINARY_INV 大于T被设置为0,其他的小于等于T的呗设置为255.
"""
import cv2 as cv
import numpy as np

image = cv.imread("pic/14.png")
gray = cv.cvtColor(image, cv.COLOR_BGR2GRAY)
blurred = cv.GaussianBlur(gray, (7, 7), 0)
cv.imshow("Image", image)
cv.imshow("Blurred", blurred)
cv.waitKey(0)

T, thresInv = cv.threshold(blurred, 200, 255, cv.THRESH_BINARY_INV)
cv.imshow("Threshold_Binary_Inverse", thresInv)

T1, thres = cv.threshold(blurred, 200, 255, cv.THRESH_BINARY)
cv.imshow("Threshold_Binary", thres)

cv.waitKey(0)


"""
大律法阈值分割:
对于简单的阈值分割,我们要手动提供一个阈值T,大律法是假定我们的图像包含两类像素:背景和前景.
此外,OTSU的方法假设图像的像素强度的灰度直方图是双峰的.查看如下两幅图的直方图.
然后基于直方图,OTSU方法计算最佳阈值T,以使得背景峰和前景峰之间的差异最小.
但是OTSU的方法没有先验知识哪些像素属于前景,哪些像素属于背景-它只是试图以最佳方式分离直方图的峰.
OTSU方法时全局阈值化的一个示例,这意味着将位整个图像计算一个T值.在某些情况下可能是不适合的.

如果灰度图像不遵循双峰分布,这OTSU的方法仍将运行,但是可能无法提供预期的结果.
"""
T2,thresInv = cv.threshold(blurred,0,255,cv.THRESH_BINARY_INV|cv.THRESH_OTSU)
cv.imshow("Threshold",thresInv)
print("Otsu's threshold value = {}".format(T2))
cv.waitKey(0)

cv.imshow("Output",cv.bitwise_and(image,image,mask=thresInv))
cv.waitKey(0)
"""
自适应阈值.我们使用简单的阈值分割的时候需要手动的设置一个阈值T,针对于不同的图像,就可能需要不一样的T值.
为了帮助我们自动的确定T的值,我们利用了Otsu的方法.虽然大律法可以为我们节省了大量的时间,留给我们一个单一的阈值.
但是有些图像使用大律法的分割效果可能不是很好,这个时候我们就要使用自适应阈值.

自适应阈值,它仅仅考虑像素的小邻域,然后找到每个小邻域的最佳阈值T.这种方法使得我们了能够处理像素强度范围可能很大且T的最佳值可能随图像的不同部分而变化的情况.
在这里我们提供了一个值cv.ADAPTIVE_THRES_MEAN_C表示我们正在使用局部像素邻域的算术平均值来计算T的阈值.
如果提供了cv.ADAPTIVE_THRES_GAUSSIAN_C表示我们使用高斯平均值.
表示阈值方法cv.THRES_BINARY_INV表示任何通过阈值阈值测试的像素的值输出为0,否则就为255
第五个参数表示我们的像素邻域的大小.在这里我们可以看到.我们将每个计算的平均灰度像素亮度是是25*25图像中的子区域来计算我们的阈值T.
这个值是让我们微调阈值.在某些情况下,仅仅靠平均值无法在背景和前景进行足够的区分.通过增加或者减去一些值C,可以改善我们阈值的结果.
"""

from skimage.filters import threshold_local

T = threshold_local(blurred,29,offset=5,method="gaussian")
thresh = (blurred < T).astype('uint8')*255
cv.imshow("Scikit-Image Mean Thresh",thresh)
print("T = {}".format(T))
cv.waitKey(0)


image = cv.imread("pic/15.png",cv.IMREAD_GRAYSCALE)
T,thres = cv.threshold(image,0,255,cv.THRESH_BINARY|cv.THRESH_OTSU)
print(T)
cv.imshow("Thres",thresh)
cv.waitKey(0)








